package com.katesoft.scale4j.agent;

import com.katesoft.scale4j.log.Logger;
import com.katesoft.scale4j.log.LogFactory;
import com.katesoft.xml.jvmcluster.ApplicationConfigurationDocument;
import com.katesoft.xml.jvmcluster.ApplicationConfigurationDocument.ApplicationConfiguration;
import org.apache.commons.io.IOUtils;
import org.apache.commons.lang.builder.ReflectionToStringBuilder;
import org.apache.commons.lang.builder.ToStringStyle;
import org.springframework.beans.factory.InitializingBean;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Required;
import org.springframework.core.io.ClassPathResource;
import org.springframework.oxm.xmlbeans.XmlBeansMarshaller;

import javax.xml.transform.stream.StreamSource;
import java.io.IOException;
import java.io.InputStream;

/**
 * this class is responsible for parsing appConfiguration.xml
 *
 * @author kate2007
 */
public class ApplicationConfigurationReader implements InitializingBean
{
    private Logger logger = LogFactory.getLogger(getClass());
    private org.springframework.oxm.xmlbeans.XmlBeansMarshaller marshaller;

    public ApplicationConfiguration parseConfiguration(InputStream inputStream) throws IOException
    {
        try {
            long time = System.currentTimeMillis();
            StreamSource source = new StreamSource(inputStream);
            ApplicationConfiguration cfg = ((ApplicationConfigurationDocument) marshaller.unmarshal(source)).getApplicationConfiguration();
            logger.debug("parsed application_configuration %s from %s in [%s milisecs]",
                         ReflectionToStringBuilder.reflectionToString(cfg, ToStringStyle.MULTI_LINE_STYLE), inputStream.toString(),
                         (System.currentTimeMillis() - time));
            return cfg;
        }
        finally {
            IOUtils.closeQuietly(inputStream);
        }
    }

    public ApplicationConfiguration parseConfiguration(String appConfigurationLocation) throws IOException
    {
        ClassPathResource classPathResource = new ClassPathResource(appConfigurationLocation);
        return parseConfiguration(classPathResource.getInputStream());
    }

    @Autowired
    @Required
    public void setMarshaller(XmlBeansMarshaller marshaller)
    {
        this.marshaller = marshaller;
    }

    @Override
    public void afterPropertiesSet() throws Exception
    {
        marshaller.setValidating(true);
    }
}
